# $Id: netops.py 7557b5d4d82b 2012/12/02 09:07:16 pgurumur $
# Copyright (c) 2009 Prabhu Gurumurthy  <pgurumur@gmail.com>
# 
# Permission to use, copy, modify, and distribute this software for any
# purpose with or without fee is hereby granted, provided that the above
# copyright notice and this permission notice appear in all copies.
#
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
#

import getpass
import itertools
import optparse
import sys

from djanet.db import netdb, ssndb
from djanet.lib import ip
from djanet.lib.exception import AppError
from djanet.tools.lib import backup, getopts

class Command(getopts.GetOptions):
   option_list = (
         optparse.make_option("-b", "--backup", action = "store_true",
            help = "Backup device(s) and update/add to subversion",
            default = False, dest = "backup"),
         optparse.make_option("-C", "--console", action = "store_true",
            help = "List console information for the device",
            dest = "console"),
         optparse.make_option("-i", "--ip", action = "store", default = 0,
            type = "choice", choices = ["4", "6"],
            help = "List IP addresses for a given family 4 = ipv4, 6 = ipv6",
            dest = "ip"),
         optparse.make_option("-I", "--interfaces", action = "store_true",
            help = "List all interfaces for device(s)",
            dest = "interfaces"),
         optparse.make_option("-S", "--sleep", type = "int",
            help = "Sleep time to wait for system backup, default: 240",
            default = 240, dest = "sleep"),
         optparse.make_option("-s", "--ssh", action = "store_true",
            help = "SSH option for running scripts on server", dest = "ssh"),
         optparse.make_option("-l", "--login", type = "str",
            help = "Username for ssh option to login to host",
            default = getpass.getuser(), dest = "login"),
         optparse.make_option("-f", "--filename", type = "str",
            help = "Script to push to the server using -s/--ssh option",
            dest = "filename"),
         ) + getopts.GetOptions.option_list

   def __init__(self):
      super(Command, self).__init__()
      self.prog = __file__.split("/")[-1]
      self._host = []

   def handle(self, *args, **options):
      try:
         self._host = args[0:]
      except IndexError:
         pass

      cfgbackup = options.get("backup")
      ip = options.get("ip")
      interfaces = options.get("interfaces")
      ssh = options.get("ssh")
      console = options.get("console")
      if cfgbackup:
         sleep = options.get("sleep")
         retval = backup.configbackups(self._host, sleep)
         if retval:
            self.error(retval)
      elif ip:
         if int(ip) == 4:
            for ix in netdb.Ipblock.objects.filter(version = 4).all():
               print(ix)
         elif int(ip) == 6:
            for ix in netdb.Ipblock.objects.filter(version = 6).all():
               print(str(ix).lower())

            for ix in ssndb.Ipv6Prefix.objects.using('ssn').all():
               print(str(ix).lower())
      elif interfaces:
         device = []
         for ix, jy in itertools.product(netdb.Device.objects.all(),
               self._host):
            if str(ix.ip) == str(jy):
               device.append(ix)

         for ix in device:
            print ix.GetInterfacesIP(), ix.Product.entity,
            print ix.Product.Type, ix.ip, ix.Site, ix.interfaces,
            print ix.bgpid
      elif ssh:
         username = options.get("login").strip()
         filename = None
         if hasattr(options, "filename"):
            filename = options.get("filename").strip()

         password = None
         if username:
            password = getpass.getpass("%s password: " %username)
         else:
            self.error("%s: cannot proceed without username", prog)

         sshclient = []
         for system in self._host:
            device = util.ConfigPush(util.ssh(hostname = system,
               username = username, password = password,
               verbose = bool(options.verbosity), filename = filename),
               system, bool(options.verbosity))
            sshclient.append(device)
            device.setName(device)
            device.start()

         for dev in sshclient:
            dev.join()
      elif console:
         devices = []
         for jy, ix in itertools.product(
               netdb.Device.objects.all(), self._host):
            if str(jy.ip) == str(ix):
               devices.append(jy)

         for ix in devices:
            print(ix.Attr)
